package com.ansion.utils.thread;

import android.app.Activity;
import android.content.Context;
import android.view.View;

import androidx.fragment.app.Fragment;

import com.ansion.log.S;
import com.ansion.log.VLog;
import com.ansion.utils.lifecycle.BaseLifeCircle;

/**
 * created by zhaoyuntao
 * on 2019-10-27
 * description:
 */
public abstract class SafeRunnable extends BaseLifeCircle implements Runnable {
    private long startTime;
    private long endTime;
    private String stackInfo;

    public SafeRunnable(Activity lifeCircle) {
        super(lifeCircle);
        initStackInfo();
    }

    public SafeRunnable(Fragment lifeCircle) {
        super(lifeCircle);
        initStackInfo();
    }

    public SafeRunnable(android.app.Fragment lifeCircle) {
        super(lifeCircle);
        initStackInfo();
    }

    public SafeRunnable(Context lifeCircle) {
        super(lifeCircle);
        initStackInfo();
    }

    public SafeRunnable(View lifeCircle) {
        super(lifeCircle);
        initStackInfo();
    }

    private void initStackInfo() {
        if (VLog.OPEN_LOG) {
            this.stackInfo = S.getStackInfo(7, 4);
        }
    }

    protected abstract void runSafely();

    protected void beforeRun() {}

    protected void afterRun() {}

    private void _beforeRun() {
        if (VLog.OPEN_LOG) {
            startTime = System.currentTimeMillis();
        }
    }

    private void _afterRun() {
        if (VLog.OPEN_LOG) {
            endTime = System.currentTimeMillis();
            long cost = endTime - startTime;
            Object o = get();
            String className = o == null ? "Unknown" : o.getClass().getSimpleName();
            if (cost > 30) {
                String log = "(Time-consuming SafeRunnable found from[" + className + "] start:" + startTime + "  end:" + endTime + "  cost:" + cost + "ms) StackTrace:" + stackInfo;
                VLog.e("TAG_UI_TRACK", log);
//                BL.e(log);
            }
        }
    }

    @Override
    public void run() {
        if (checkLifeCircle()) {
            _beforeRun();
            beforeRun();
            runSafely();
            _afterRun();
            afterRun();
        }
    }
}

